package com.java.permission.common.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.java.permission.common.dao.entity.SysUser;
import com.java.permission.common.dao.mapper.SysUserMapper;
import com.java.permission.common.dto.SysUserDto;
import com.java.permission.common.enums.DataStatusEnum;
import com.java.permission.common.enums.PapersTypeEnums;
import com.java.permission.common.exception.ParamsException;
import com.java.permission.common.params.PageParams;
import com.java.permission.common.service.BaseService;
import com.java.permission.common.service.SysUserService;
import com.java.permission.common.utils.IdUtils;

import org.apache.commons.collections4.CollectionUtils;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.BeanUtils;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import javax.annotation.Resource;
import java.time.LocalDateTime;
import java.util.List;



/**
 * @author hu
 * @version 1.0
 * @date 2020/6/12 16:26
 * @description
 */
@Service
public class UserServiceImpl extends BaseService implements SysUserService {

    @Resource
    private SysUserMapper sysUserMapper;

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void save (SysUserDto sysUserDto, String operUserId) {
        //todo 校验手机号等是否存在
        SysUser sysUser = new SysUser();
        LocalDateTime now = LocalDateTime.now();
        BeanUtils.copyProperties(sysUserDto, sysUser);
        sysUser.setId(IdUtils.newId());
        sysUser.setLastLoginDate(now);
        sysUser.setCreateAt(now);
        sysUser.setCreateBy(operUserId);
        sysUser.setUpdateAt(now);
        sysUser.setUpdateBy(operUserId);
        sysUser.setSource(0);
        sysUser.setStatus(Integer.valueOf(DataStatusEnum.NORMAL.getCode()));
        sysUserMapper.insert(sysUser);
    }

    /**
     * 校验参数
     * @param sysUserDto
     */
    @Override
    public void validUserParams(SysUserDto sysUserDto) {
        if (sysUserDto.getPapersType() == null) {
            throw new ParamsException("请选择证件类型！");
        }
        if (PapersTypeEnums.IDCARD.getCode().equals(sysUserDto.getPapersType()) &&  StringUtils.isBlank(sysUserDto.getIdCard())) {
            throw new ParamsException("请输入身份证号码！");
        }
        if (PapersTypeEnums.PASSPORT.getCode().equals(sysUserDto.getPapersType()) &&  StringUtils.isBlank(sysUserDto.getPassport())) {
            throw new ParamsException("请输入护照号码！");
        }
        //todo 手机 邮箱 证件 等 格式合法性校验
        LambdaQueryWrapper<SysUser> query = new LambdaQueryWrapper<>() ;
        if (StringUtils.isNotBlank(sysUserDto.getId())) {
            query.ne(SysUser::getId, sysUserDto.getId());
        }
        query.ne(SysUser::getStatus, DataStatusEnum.DETELE.getCode()).and(qw -> {
            qw.eq(SysUser::getUsername, sysUserDto.getUsername())
              .or().eq(SysUser::getEmail, sysUserDto.getEmail())
              .or().eq(SysUser::getPhone,sysUserDto.getPhone())
              .or().eq(SysUser::getMobile, sysUserDto.getMobile())
            ;
            if (StringUtils.isNotBlank(sysUserDto.getIdCard())) {
                qw.or().eq(SysUser::getIdCard, sysUserDto.getIdCard());
            }
            if (StringUtils.isNotBlank(sysUserDto.getPassport())) {
                qw.or().eq(SysUser::getPassport, sysUserDto.getPassport());
            }
        });
        SysUser sysUser = sysUserMapper.selectOne(query);
      if (sysUser != null) {
          if (sysUser.getPhone().equals(sysUserDto.getPhone())) {
              throw  new ParamsException("当前电话号码已存在！");
          }
          if ( sysUser.getIdCard() != null && sysUser.getIdCard().equals(sysUserDto.getIdCard())) {
              throw new ParamsException("当前身份证号码已存在");
          }
          if (sysUser.getPassport() != null && sysUser.getPassport().equals(sysUserDto.getPassport())) {
              throw new ParamsException("当前护照号码已存在");
          }
          // todo 校验其他唯一字段
      }
    }


    @Override
    public List<SysUser> findValidAll() {
        QueryWrapper<SysUser> queryWrapper = new QueryWrapper<>();
        queryWrapper.lambda().ne(SysUser::getStatus, DataStatusEnum.NORMAL.getCode());
        return sysUserMapper.selectList(queryWrapper);
    }

    @Override
    public IPage<SysUser> findValidPageBy(PageParams pageParams) {
        Page<SysUser> sysUserPage = new Page<>(pageParams.getPageNum(), pageParams.getPageSize());
        LambdaQueryWrapper<SysUser> query = new LambdaQueryWrapper<>();
        query.ne(SysUser::getStatus, DataStatusEnum.DETELE.getCode());
        return sysUserMapper.selectPage(sysUserPage, query);
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void edit(SysUserDto sysUserDto, String operUserId) {
        SysUser forUpdate = this.checkUserIsExistByUserId(sysUserDto.getId());
        if (forUpdate == null) {
            throw new ParamsException("当前用户不存在！");
        }
        BeanUtils.copyProperties(sysUserDto, forUpdate, "password");
        forUpdate.setUpdateAt(LocalDateTime.now());
        forUpdate.setUpdateBy(operUserId);
        sysUserMapper.updateById(forUpdate);
    }


    @Override
    public SysUser findById(String id) {

        LambdaQueryWrapper<SysUser> query = new LambdaQueryWrapper<>();
        query.eq(SysUser::getId, id).ne(SysUser::getStatus, DataStatusEnum.DETELE.getCode());
        SysUser sysUser = sysUserMapper.selectOne(query);
        if (sysUser == null) {
            throw new ParamsException("当前用户不存在!");
        }
        SysUserDto sysUserDto = new SysUserDto();
        BeanUtils.copyProperties(sysUser, sysUserDto, "password");
        return sysUser;
    }

    @Override
    public List<SysUser> findByUserIdIn(List<String> userIdList) {
        if (CollectionUtils.isNotEmpty(userIdList)) {
            LambdaQueryWrapper<SysUser> query = new LambdaQueryWrapper<>();
            query.ne(SysUser::getStatus, DataStatusEnum.DETELE.getCode()).in(SysUser::getId, userIdList);
           return sysUserMapper.selectList(query);
        }
        return null;
    }

    /**
     * 校验用户是否存在
     * @param userId
     * @return
     */
    private  SysUser checkUserIsExistByUserId(String userId) {
        QueryWrapper<SysUser> query = new QueryWrapper<>();
        query.lambda().ne(SysUser::getStatus, DataStatusEnum.DETELE.getCode()).ne(SysUser::getId, userId);
        return sysUserMapper.selectOne(query);
    }

}
